require("prefabutil")

local assets =
{
    Asset("ANIM", "anim/sw_shadowwoven_tower.zip"), -- 后续改
}

local prefabs =
{
    "collapse_small",
}

local function onhammered(inst, worker)
    inst.components.lootdropper:DropLoot()
    local fx = SpawnPrefab("collapse_small")
    fx.Transform:SetPosition(inst.Transform:GetWorldPosition())
    fx:SetMaterial("stone")
    inst:Remove()
end

local function onhit(inst, worker)
    if inst.components.prototyper.on then
        inst.AnimState:PlayAnimation("hit_open")
        inst.AnimState:PushAnimation("proximity_loop", true)
    else
        inst.AnimState:PlayAnimation("hit_close")
        inst.AnimState:PushAnimation("idle", false)
    end
end

local function doonact(inst)
    if inst._activecount > 1 then
        inst._activecount = inst._activecount - 1
    else
        inst._activecount = 0
    end
end

local function onturnon(inst)
    if inst._activetask == nil then
        if inst.AnimState:IsCurrentAnimation("proximity_loop") then
            -- 如果其他动画仍在队列中
            inst.AnimState:PlayAnimation("proximity_loop", true)
        elseif inst.AnimState:IsCurrentAnimation("use") then
            inst.AnimState:PlayAnimation("proximity_loop", true)
        else
            if inst.AnimState:IsCurrentAnimation("place") then
                inst.AnimState:PushAnimation("proximity_pre")
            else
                inst.AnimState:PlayAnimation("proximity_pre")
            end
            inst.AnimState:PushAnimation("proximity_loop", true)
        end
    end
    if not inst.SoundEmitter:PlayingSound("loopsound") then
        inst.SoundEmitter:PlaySound("rifts/forge/proximity_lp", "loopsound")
    end
end

local function onturnoff(inst)
    if inst._activetask == nil then
        inst.AnimState:PushAnimation("proximity_pst")
        inst.AnimState:PushAnimation("idle", false)
        inst.SoundEmitter:PlaySound("rifts/forge/proximity_pst")
    end
    inst.SoundEmitter:KillSound("loopsound")
end

local function doneact(inst)
    inst._activetask = nil
    if inst.components.prototyper.on then
        onturnon(inst)
    else
        onturnoff(inst)
    end
end

local function onactivate(inst)
    inst.AnimState:PlayAnimation("use")
    inst.SoundEmitter:PlaySound("rifts/forge/use")
    inst._activecount = inst._activecount + 1
    inst:DoTaskInTime(1.5, doonact)
    if inst._activetask ~= nil then
        inst._activetask:Cancel()
    end
    inst._activetask = inst:DoTaskInTime(inst.AnimState:GetCurrentAnimationLength(), doneact)
end

local function onbuilt(inst, data)
    inst.AnimState:PlayAnimation("place")
    inst.AnimState:PushAnimation("idle", false)
    inst.SoundEmitter:PlaySound("rifts/forge/place")
end

local function remove_sw_shadowwoven_tower(player)
    if player.sw_shadowwoven_tower ~= nil then
        player.sw_shadowwoven_tower = nil
    end
    if player.sw_task ~= nil then
        player.sw_task:Cancel()
        player.sw_task = nil
    end
end

local function OnTick(inst)
    local x, y, z = inst.Transform:GetWorldPosition()
    local players = FindPlayersInRange(x, y, z, 25, true)
    for k, player in pairs(players) do
        player.sw_shadowwoven_tower = 1
        player:AddDebuff("sw_buff_shadowwoven_tower", "sw_buff_shadowwoven_tower")
        if player.sw_task ~= nil then
            player.sw_task:Cancel()
            player.sw_task = nil
        end
        player.sw_task = player:DoTaskInTime(7, remove_sw_shadowwoven_tower)
    end
end

-- 根据当前世界状态，决定灯光是开还是关
local function RecalcLightPhase(inst)
    if TheWorld:HasTag("cave") then
        inst.Light:Enable(true)
        inst.AnimState:SetBloomEffectHandle("shaders/anim.ksh")
    else
        local phase = TheWorld.state.phase
        if phase == "night" then
            inst.Light:Enable(true)
            inst.AnimState:SetBloomEffectHandle("shaders/anim.ksh")
        else
            inst.Light:Enable(false)
            inst.AnimState:ClearBloomEffectHandle()
        end
    end
end

-- 睡醒回调
local function OnEntityWake(inst)
    if inst.task == nil then
        inst.task = inst:DoPeriodicTask(5, OnTick, nil)
    end
end
local function OnEntitySleep(inst)
    if inst.task ~= nil then
        inst.task:Cancel()
        inst.task = nil
    end
end

local function fn()
    local inst = CreateEntity()

    inst.entity:AddTransform()
    inst.entity:AddAnimState()
    inst.entity:AddMiniMapEntity()
    inst.entity:AddSoundEmitter()
    inst.entity:AddLight()
    inst.entity:AddNetwork()

    inst:SetDeploySmartRadius(DEPLOYSPACING_RADIUS[DEPLOYSPACING.DEFAULT] / 2)
    MakeObstaclePhysics(inst, .4)

    inst.MiniMapEntity:SetPriority(5)
    inst.MiniMapEntity:SetIcon("sw_shadowwoven_tower.tex") -- 小地图图标

    inst.AnimState:SetBank("sw_shadowwoven_tower")         -- 后续改
    inst.AnimState:SetBuild("sw_shadowwoven_tower")        -- 后续改
    inst.AnimState:PlayAnimation("idle")
    inst.Transform:SetScale(1.2, 1.2, 1)

    inst.Light:SetColour(1, 1, 1) -- 白色光
    inst.Light:SetRadius(5)       -- 设置光照范围
    inst.Light:SetFalloff(0.6)    -- 设置光照衰减率
    inst.Light:SetIntensity(0.6)  -- 设置光照强度
    inst.Light:Enable(true)

    inst.AnimState:SetBloomEffectHandle("shaders/anim.ksh") -- 加个泛光,游戏中可以在官方设置中开启关闭

    inst:AddTag("structure")
    inst:AddTag("sw_shadowwoven_tower")
    inst:AddTag("lunar_forge")
    inst:AddTag("shadow_forge")

    inst:AddTag("prototyper")

    MakeSnowCoveredPristine(inst)

    inst.entity:SetPristine()

    if not TheWorld.ismastersim then
        return inst
    end

    inst._activecount = 0
    inst._activetask = nil

    inst:AddComponent("inspectable")
    inst:AddComponent("prototyper")
    inst.components.prototyper.onturnon = onturnon
    inst.components.prototyper.onturnoff = onturnoff
    inst.components.prototyper.onactivate = onactivate
    inst.components.prototyper.trees = TUNING.PROTOTYPER_TREES.SW_SHADOWWOVEN_TECH_ONE

    inst:ListenForEvent("onbuilt", onbuilt)

    inst:AddComponent("lootdropper")
    inst:AddComponent("workable")
    inst.components.workable:SetWorkAction(ACTIONS.HAMMER)
    inst.components.workable:SetWorkLeft(4)
    inst.components.workable:SetOnFinishCallback(onhammered)
    inst.components.workable:SetOnWorkCallback(onhit)

    MakeSnowCovered(inst)

    inst:AddComponent("hauntable")
    inst.components.hauntable:SetHauntValue(TUNING.HAUNT_TINY)

    inst.OnEntityWake  = OnEntityWake
    inst.OnEntitySleep = OnEntitySleep

    inst:WatchWorldState("phase", RecalcLightPhase)
    RecalcLightPhase(inst)

    return inst
end

return Prefab("sw_shadowwoven_tower", fn, assets, prefabs),
    MakePlacer("sw_shadowwoven_tower_placer", "sw_shadowwoven_tower", "sw_shadowwoven_tower", "idle", nil, nil, nil, 1.2) -- 后续改
